#pragma once
#include "GridNode.h"

class GridRunner
{
public:
	GridRunner();
	~GridRunner();
	void run(GridNode& start, GridNode& goal);

	// ---- Constants ----
	static const int DEFAULT_OPEN_CAPACITY = 1000000;
	static const int DEFAULT_CLOSED_CAPACITY = 1000000;
	static const int NUM_OF_OPS = 8;
	// Node statuses
	static const int STATUS_NEW = 0;
	static const int STATUS_OPEN = 1;
	static const int STATUS_CLOSED = 2;


private:
	void insertToOpen(GridNode* node, int f);
	void expand(GridNode* pTopNode);
	void reorder(int pCurrentIndex);
	GridNode* move(GridNode* pNode, int pOpIndex);
	void removeFromOpen(int pHeapIndex);
	GridNode* popOpen();
	int find(GridNode* pNode, int pNodeStatus);
	int findNodeStatus(GridNode* pNode);
	bool isGoal(GridNode* pNode);
	int h(GridNode& pNode);
	void reopen(int pNodeIndex);
	bool isLegalOp(GridNode* pNOde, int pOpIndex);
	GridNode** openlist;
	int openCapacity;
	int openSize;
	int goalX;
	int goalY;
	int startX;
	int startY;

	// Closed list related functions
	GridNode**  closedlist;
	int closedCapacity;
	int closedSize;
	void removeFromClosed(int pIndex);
	void insertToClosed(GridNode* pNode);

	// Heap related functions
	int heapifyDown(int pHeapIndex);
	int heapifyUp(int pHeapIndex);
	inline int childLeft(int index);
	inline int childRight(int index);
	inline int parent(int index);
	bool testAndSwapOpen(int pParent,int pChild);


};



